package message;

import org.apache.activemq.ActiveMQConnection;
import org.apache.activemq.ActiveMQConnectionFactory;
import org.apache.activemq.command.ActiveMQTopic;

import javax.jms.*;
import java.util.Objects;

/**
 * 消息头
 *
 * @author Guojt
 * @date 2024/10/31 18:17
 */
public class MessageHead implements MessageListener {
    private static String USERNAME = ActiveMQConnection.DEFAULT_USER;
    private static String PASSWORD = ActiveMQConnection.DEFAULT_PASSWORD;
    private static String BROKER = ActiveMQConnection.DEFAULT_BROKER_URL;

    private static String TOPIC_NAME = "topic";

    /**
     * 消息的组成： 消息头 + 消息体 + 消息属性 + 消息自身
     *
     * @param message
     */
    @Override
    public void onMessage(Message message) {


        // 创建主题连接工厂
        TopicConnectionFactory conFactory = new ActiveMQConnectionFactory(USERNAME, PASSWORD, BROKER);
        /**
         *  JMS消息头 分为： 自动分配的消息头 和 开发者分配的消息头
         */

        try {
            TopicConnection topicConnection = conFactory.createTopicConnection();
            if(Objects.isNull(topicConnection)){
                System.out.println("topicConnection is null");
            }


            TopicSession topicSession = topicConnection.createTopicSession(true, Session.AUTO_ACKNOWLEDGE);
            Topic topic = new ActiveMQTopic(TOPIC_NAME);
            TopicPublisher publisher = topicSession.createPublisher(topic);


            // 启动连接
            topicConnection.start();


            /**
             * 自动分配的消息头  ----------------------
             */
            // 消息头使用 topic 和 Queue 对象来识别 目的地 （都实现了Destination）
            Topic jmsDestination = (Topic) message.getJMSDestination();


            // 传送模式： 持久性模式和非持久性模式
            /**
             *  1： 持久性模式： 一条消息应该被发送一次并且只发送一次， 在发送过程中jsm 提供者故障 ，该消息可以重传
             *  2： 非持久性模式： 一条消息最多发送一次， 在发送过程中jsm 提供者故障 ，该消息不会重传，可能会丢失
             */
            int persistent = DeliveryMode.PERSISTENT; //2
            int nonPersistent = DeliveryMode.NON_PERSISTENT; //1
            int jmsDeliveryMode = message.getJMSDeliveryMode();
            if (jmsDeliveryMode == persistent) {
                System.out.println("消息是持久型模式");
            } else if (jmsDeliveryMode == nonPersistent) {
                System.out.println("消息是非持久型模式");
            }
            publisher.setDeliveryMode(persistent); // 设置持久性模式


            /**
             * JSMessageID 标识了一条消息的唯一。  JSMessageID 可以和 JSMessageID 结合使用用与消息关联
             */
            String jmsMessageID = message.getJMSMessageID();
            // 获取时间戳 毫秒，表示 消息发送的时间和消息接收的时间 之间的时间差
            long jmsTimestamp = message.getJMSTimestamp();

            // 消息的有效期，单位为毫秒
            long jmsExpiration = message.getJMSExpiration();
            message.setJMSExpiration(3600000);//一小时 如果设置0 表示消息永不过期，默认是0

            // 表示消息将被重新传送给消费者 true
            boolean jmsRedelivered = message.getJMSRedelivered();
            message.setJMSRedelivered(true);


            /**
             *  获取消息的优先级
             *    一共分为两类 ： 0-4是普通的  和 5-9是加急的
             *   是在生产者中设置
             */
            publisher.setPriority(9);
            int jmsPriority = message.getJMSPriority();




            /**
             * 开发者分配的消息头  ----------------------
             */
            // 可能生产者会要求消费者回复消息，那么在发送消息的时候，需要设置一个回复目的地 Destination
            // TODO 问题
            message.setJMSReplyTo(topic);
            Topic jmsReplyTo = (Topic) message.getJMSReplyTo();

            // 将一条消息标记为对 jmsMessageID 标记的上一条消息的应答
            message.setJMSCorrelationID(jmsMessageID);

            // 获取消息的类型
            String jmsType = message.getJMSType();
        } catch (JMSException e) {
            throw new RuntimeException(e);
        }
    }
}
